

/**
 * 游戏玩法界面
 */

import { HandItem_blxf } from "../Common/handItem";
import GameData_blxf from "../GameData/GameData";
import BaseShopData_blxf from "../GameData/ShopData";
import { BaseTargetData_blxf } from "../GameData/TargetData";
import { BaseVendorData_blxf, VendorData_blxf } from "../GameData/VendorData";
import { CsvManager_blxf } from "../Manager/CsvManager";
import { EnumManager_blxf } from "../Manager/EnumManager";
import PageManager_blxf from "../Manager/PageManager";
import { PlatformManager_blxf } from "../Manager/PlatformManager";
import AudioModule_blxf from "../Module/AudioModule";
import { ConfigModule_blxf } from "../Module/ConfigModule";
import { LoadModule_blxf } from "../Module/LoadModule";
import { NumModule_blxf } from "../Module/NumModule";
import PublicModule_blxf from "../Module/PublicModule";
import { UtilsModule_blxf } from "../Module/UtilsModule";
import GuestPanel_blxf from "./guestPanel";
import TargetItem_blxf from "./targetItem";
import VendorItem_blxf from "./vendorItem";

const {ccclass, property} = cc._decorator;

@ccclass
export default class VendorPanel_blxf extends cc.Component {

    @property({ type: cc.Node, tooltip: '背景图' })
    bgNode: cc.Node = null;

    @property({ type: cc.Node, tooltip: '按钮层' })
    btnBox: cc.Node = null;

    @property({ type: cc.Node, tooltip: '客人面板' })
    guestBox: cc.Node = null;

    @property({ type: cc.Prefab, tooltip: '摊位item' })
    vendorItem: cc.Prefab = null;

    @property({ type: cc.Prefab, tooltip: '菜篮子item' })
    targetItem: cc.Prefab = null;

    @property({ type: cc.Node, tooltip: '摊位盒子' })
    vendorBox: cc.Node = null;

    @property({ type: cc.Node, tooltip: '菜篮子盒子' })
    targetBox: cc.Node = null;

    @property({ type: cc.Node, tooltip: '剩余补货数' })
    addShopNumNode: cc.Node = null;

    @property({ type: cc.Node, tooltip: '10个物品回收篮' })
    allShopTargetNode: cc.Node = null;

    @property({ type: [cc.Node], tooltip: '适配节点列表' })
    nodeList: cc.Node[] = [];

    @property({ type: cc.Node, tooltip: '福贴按钮盒子' })
    coupletBtnBox: cc.Node = null;

    @property({ type: cc.Node, tooltip: '上货按钮' })
    addShopBtn: cc.Node = null;

    @property({ type: cc.Node, tooltip: '手指动画节点' })
    handItemNode: cc.Node = null;

    @property({ tooltip: '手指引导倒计时' })
    _handTimer: number = -1;
    
    @property({ tooltip: '运行帧数'})
    _dtNum: number = 0;

    @property({ tooltip: '关卡、货币信息' })
    _topInfoPfName: string = 'vendorInfoPanel';

    @property({ tooltip: '游戏按钮层' })
    _gameBtnPfName: string = 'gameBtnList';

    @property({ tooltip: '临时菜篮子商品id' })
    _videoShopId: number = -1;

    @property({ tooltip: '上货总数'})
    _addShopNum: number = 0;
    @property({ tooltip: '上货失败次数' })
    _addShopFailNum: number = 0;


    @property({ tooltip: '标记摊位this' })
    _vendorItemThis: VendorItem_blxf = null;

    @property({ tooltip: '是否点击' })
    _isClick: boolean = false;

    @property({ tooltip: '是否展示满物品菜篮子' })
    _isAllShopTarget: boolean = true;

    @property({ tooltip: '满物品菜篮子动画' })
    _allShopBtnTween: cc.Tween = null;

    @property({ tooltip: '收货郎动画' })
    _allShopGuest: sp.Skeleton = null;

    @property({ tooltip: '是否正在播收货郎动画' })
    _isAllShopGuestAnimation: boolean = false;

    @property({ tooltip: '收货郎动画名' })
    _allShopGuestAnimationName: string = null;

    @property({ tooltip: '放入菜篮子商品id' })
    _touchTargetShopId: number = null;

    @property({ tooltip: '过关菜篮子id' })
    _passTargetId: number = 1;


    @property({ tooltip: '累计送货次数' })
    _totalBuyNum: number = 0;

    _isLoad: boolean = false;


    @property({ tooltip: '自定义事件累计id' })
    _reportEventId: number = 2;

    // LIFE-CYCLE CALLBACKS:

    
    onLoad () {
        this._isLoad = false;
        this._totalBuyNum = 0;

        this._reportEventId = 2;
        this._isAllShopTarget = true;
        PublicModule_blxf.isGame = true;
        PublicModule_blxf.coupletParentList[1] = this.coupletBtnBox;


        this.scheduleOnce(()=>{
            this.initSize_blxf();
        })

        this.initEvent_blxf();
    }

    start () {
        this._topInfoPfName = 'vendorInfoPanel';
        this._gameBtnPfName = EnumManager_blxf.prefabNameType.PREFAB_GAME_BTN;
    }

    onDestroy () { 
        cc.game.removeAll(this);
    };

    update ( dt: number ) {
        if ( !this._isLoad ) return;

        let _isLoadOk: boolean;
        _isLoadOk = this.loadVendorList_blxf();
        if ( !_isLoadOk ) return;

        _isLoadOk = this.loadTargetList_blxf();
        if ( !_isLoadOk ) return;

        this._dtNum += 1;

        // 手指引导倒计时
        this.onTimer_demo( dt );
        // 自动送货
        this._dtNum == 5 && this.onAddVendorShopList_blxf();

        this._dtNum % 21 == 0 && this.onCheckAllShopBtn_blxf();

        if ( this._dtNum > 20 ) PublicModule_blxf.isLoadUiOk = true;

        PublicModule_blxf.setOpenPanelNode_blxf( null );
    }

    /** 随机播放背景音乐 */
    playGameBgm_blxf () {
        AudioModule_blxf.instance.onRandomGameBgm_blxf();
    }

    /** 初始化页面尺寸 */
    initSize_blxf () {
        UtilsModule_blxf.instance.setNodeSize_blxf( this.node );

        let { checkH, isIpad, winSizeW } = ConfigModule_blxf.instance;
        this.vendorBox.y -= checkH * 4 / 4;
        this.targetBox.y -= checkH * 3 / 4;
        this.guestBox.y -= checkH * 3 / 4;
        this.addShopNumNode.y -= checkH;
        this.allShopTargetNode.y -= checkH * 3 / 4;
        this.nodeList.forEach( (item, index) =>{
            if ( index == 1 ) item.height += checkH / 2;
            let _updateH: number;
            switch ( index ) {
                case 0 : _updateH = -checkH * 3 / 4; break;
                case 1 : _updateH = -checkH; break;
                case 2 : _updateH = checkH; break;
            }
            item.y += _updateH;
        })

        if ( isIpad ) this.bgNode.width = winSizeW;
    }

    /** 初始化事件监听 */
    initEvent_blxf () {
        cc.game.on('loadGame_blxf', this.loadGame_blxf, this);
        cc.game.on('onFirstCheckGuest_blxf', this.onFirstCheckGuest_blxf, this);
        
        cc.game.on('onShowVendorPanel_blxf', this.onShowVendorPanel_blxf, this);
        cc.game.on('onCloseVendorPanel', this.onCloseVendorPanel_blxf, this);
        cc.game.on('onEntryGameClear_blxf', this.onEntryGameClear_blxf, this);

        cc.game.on('onAddVendorShopList', this.onAddVendorShopList_blxf, this);
        cc.game.on('onRemoveVendorAllShop', this.onRemoveVendorAllShop_blxf, this);

        cc.game.on('onRestartBtnShopNum', this.restartBtnShopNum_blxf, this);

        cc.game.on('onAllShopVendorPos_blxf', this.onAllShopVendorPos_blxf, this);

        cc.game.on('onGuestTouchTarget_blxf', this.onGuestTouchTarget_blxf, this );

        cc.game.on('onCheckTargetLvUp_blxf', this.onCheckTargetLvUp_blxf, this);

        cc.game.on('onBuyAllMoveShop_blxf', this.onBuyAllMoveShop_blxf, this);

        cc.game.on('onCheckAutoUnlockTarget_blxf', this.onCheckAutoUnlockTarget_blxf, this);

        cc.game.on('loadGoldVideoPanel_blxf', this.loadGoldVideoPanel_blxf, this);
    };

    loadGame_blxf () {
        this._isLoad = true;

        // 默认加载隐藏（非首次）
        let _isGui: boolean = GameData_blxf.instance.getIsGuidance_blxf();
        !_isGui && PageManager_blxf.instance.loadGuidance_blxf( 1 );

        this.initGamePlayData_blxf();

        this.onShowVendorPanel_blxf();

        this.loadTopInfo_blxf(()=>{
            // this.loadGameBtnList_blxf();

            this.updateBtnShopNum_blxf();
        });
    }

    /** 初始化摊位数据 */
    initGamePlayData_blxf () {
        VendorData_blxf.instance.initGamePlayData_blxf();
    };

    /** 加载关卡、货币信息 */
    loadTopInfo_blxf ( callback: any ) {
        let _data: object = {
            pfName     : this._topInfoPfName,
            parentNode : this.btnBox,
            position   : cc.v2(0, 560),
            cb         : callback
        }
        PageManager_blxf.instance.LoadPrefab_blxf( _data );
    };

    /** 加载按钮层 */
    loadGameBtnList_blxf () {
        let _data = {
            pfName: this._gameBtnPfName,
            parentNode: this.btnBox
        }
        PageManager_blxf.instance.LoadPrefab_blxf( _data );
    };

    /** 加载摊位列表 */
    loadVendorList_blxf () {
        let { vendorDataList } = VendorData_blxf.instance;
        let _loadLen: number = this.vendorBox.childrenCount;
        let _isLoadOk: boolean = _loadLen >= vendorDataList.length;
        this.vendorBox.opacity = _isLoadOk ? 255 : 0;
        if ( _isLoadOk ) return true;

        let _vendorData: BaseVendorData_blxf = vendorDataList[ _loadLen ];
        this.loadVendorItem_blxf( _vendorData );
    }

    /**
     * 加载摊位item
     * @param vendorData 摊位数据
     */
    loadVendorItem_blxf ( vendorData: BaseVendorData_blxf ) {
        let { vendorId } = vendorData;
        let _options: object = {
            prefabNode : this.vendorItem,
            parentNode : this.vendorBox,
            zIndex     : 10 - vendorId,
        }
        let _vendorItemNode: cc.Node = LoadModule_blxf.instance.LoadNode_blxf( _options );
        _vendorItemNode.getComponent(VendorItem_blxf).initData_blxf( vendorData );

        _vendorItemNode.on('touchstart', this.onTouchVendor_blxf, this);
    }

    /** 加载菜篮子列表 */
    loadTargetList_blxf () {
        let { targetDataList } = VendorData_blxf.instance;
        let _loadLen: number = this.targetBox.childrenCount;
        let _isLoadOk: boolean = _loadLen >= targetDataList.length;
        this.targetBox.opacity = _isLoadOk ? 255 : 0;
        if ( _isLoadOk ) return true;

        let _targetData: BaseTargetData_blxf = targetDataList[ _loadLen ];
        this.loadTargetItem_blxf( _targetData );
    }

    /**
     * 加载菜篮子
     * @param targetData 菜篮子数据 
     */
    loadTargetItem_blxf ( targetData: BaseTargetData_blxf ) {
        let _options: object = {
            prefabNode : this.targetItem,
            parentNode : this.targetBox
        }
        let _targetItemNode: cc.Node = LoadModule_blxf.instance.LoadNode_blxf( _options );
        _targetItemNode.getComponent(TargetItem_blxf).initData_blxf( targetData );

        _targetItemNode.on('touchstart', this.onTouchTarget_blxf, this);
    }

    /** 加载收货郎动画 */
    loadAllShopGuest_blxf () {
        if ( this._allShopGuest ) return;

        let { SPINE_ALL_SHOP_GUEST } = EnumManager_blxf.gameSpineType;
        UtilsModule_blxf.instance.createSpine_blxf( SPINE_ALL_SHOP_GUEST, this.allShopTargetNode, ( skeleton: sp.Skeleton )=>{
            this._allShopGuest = skeleton;
            cc.error('allShopGuest >>>');
        });
    }

    /** 播放收货郎点赞动画 */
    onAllShopGuestAnimation_blxf ( animationName = 'breath' ) {
        let isLoop: boolean = animationName == 'breath';
        let _isHant = UtilsModule_blxf.instance.isTraditionalChinese_blxf();
        let skinName: string = _isHant ? 'ft' : 'jt';
        UtilsModule_blxf.instance.palyAnimation_blxf( this._allShopGuest, {
            skinName, animationName, isLoop
        })

        this._isAllShopGuestAnimation = true;
        this._allShopGuestAnimationName = animationName;
        let _duration: number = NumModule_blxf.instance.onAnimationTime_blxf( this._allShopGuest, animationName );
        this.scheduleOnce(()=>{
            if ( !this ) return;
            let _isHappy: boolean = this._allShopGuestAnimationName =='happy' && this._allShopGuestAnimationName != animationName
            if ( !_isHappy ) this._isAllShopGuestAnimation = false;
            !isLoop && this.onAllShopGuestAnimation_blxf();
        }, _duration);
    }
    
    /** 关闭主玩法页面 */
    onCloseVendorPanel_blxf ( isTouch: boolean = false ) {
        // 丛房间退出
        !isTouch && cc.game.emit('onUpdatePage_blxf');

        if ( isTouch ) {
            // let _isTouchOff = GameData_blxf.instance.getIsTouchOff_blxf();
            // !_isTouchOff && GameData_blxf.instance.setIsTouchOff_blxf( true );
            return this.loadCommonVendorPanel_blxf( /*_isTouchOff ? 4 :*/ 3 );
        }

        this.updateVendorPanel_blxf( false );
    };

    /** 显示主玩法页面 */
    onShowVendorPanel_blxf ( isGame: boolean = true) {
        this.playGameBgm_blxf();

        this.updateVendorPanel_blxf( true );

        cc.game.emit('initIconPosition_blxf');

        // 默认加载隐藏（非首次）
        let _isGui: boolean = GameData_blxf.instance.getIsGuidance_blxf();
        if ( PublicModule_blxf.isRestartGame ) {
            _isGui = false;
            this.scheduleOnce(()=>{
                PublicModule_blxf.isRestartGame = false;
            }, 0.1);
        }
        // let _bigPassNum = GameData_blxf.instance.getBigPassNum_blxf();
        // !_isGui && isGame && this.loadNextPanel( _bigPassNum );
    };

    /** 更新主玩法页面显示 */
    updateVendorPanel_blxf ( isShow: boolean ) {
        // this.node.x = isShow ? 0 : -99999;
        // this.node.opacity = isShow ? 255 : 0;
        cc.game.emit('onUpdateGamePlayPanel_blxf', isShow);

        // isShow && this.onEntryGameClear_blxf();
        isShow && this.loadAllShopGuest_blxf();
        
        PublicModule_blxf.isGame = isShow;

        if ( PublicModule_blxf.gamePlayPageId != 1 ) isShow = false;
        if ( isShow ) {
            this.onFirstCheckGuest_blxf();
        }

        cc.game.emit('onUpdateBtnAuthorize_blxf', isShow);
    }

    onFirstCheckGuest_blxf () {
        let _targetId: number = 3;
        let _targetData = VendorData_blxf.instance.findTargetData_blxf( _targetId );
        let _shopId: number = _targetData.getBuyShopId_blxf() || -1;
        let _isGui: boolean = GameData_blxf.instance.getIsGuidance_blxf();
        this.onCheckGuest_blxf( _targetId, !_isGui ? 10000 : _shopId );
    }

    /** 获取剩余补货数 */
    getBtnShopNum_blxf () {
        let _btnShopNum: number = GameData_blxf.instance.getBtnShopNum_blxf();
        return _btnShopNum;
    }

    /** 检测是佛需要补货 */
    onCheckIsAddShopNum_blxf () {
        let _btnShopNum = this.getBtnShopNum_blxf();
        let _isShopNum: boolean = _btnShopNum > 0;
        return _isShopNum;
    }

    /** 更新补货数 */
    updateBtnShopNum_blxf ( _btnShopNum: number = undefined) {
        if ( _btnShopNum === undefined ) _btnShopNum = this.getBtnShopNum_blxf();
        UtilsModule_blxf.setText_blxf( this.addShopNumNode, `${_btnShopNum}` );
    }

    /** 重置补货数 */
    restartBtnShopNum_blxf () {
        // 重装音效
        AudioModule_blxf.instance.playAudio_blxf( EnumManager_blxf.gameAudioType.AUDIO_SHOP_DELET );

        GameData_blxf.instance.initBtnShopNum_blxf();

        PublicModule_blxf.isAddShopAnimation = true;
        cc.game.emit('onAddShopBtnPos_blxf', ( toP: cc.Vec3 )=>{
            let _btnShopNum: number = this.getBtnShopNum_blxf();
            PageManager_blxf.instance.loadAddShopAnimation_blxf({ toP, btnShopNum: _btnShopNum, okCB: ( num: number )=>{
                this.updateBtnShopNum_blxf( num );
                PublicModule_blxf.isAddShopAnimation = num != _btnShopNum;
            }});
        })
    }

    /**
     * 加载通用弹窗
     * @param type 1空间不足、2库存不足、3老板别走、4老板留步、5温馨提示、6老板慎重、7收益双倍、8加速售卖、9金币不足
     */
    loadCommonVendorPanel_blxf ( type: number ) {
        cc.error('loadCommonVendorPanel_blxf >>');
        if ( this._isClick ) return;
        UtilsModule_blxf.instance.setClick_blxf( this );

        let consumeType: number, consumeNum: number;
        let { CSV_VENDOR_REMOVESHOP, CSV_VENDOR_ADDSHOP } = EnumManager_blxf.instance.getGameCsvType();
        let _csvName: string, _isGui1: boolean;
        switch ( type ) {
            case 1 : _csvName = CSV_VENDOR_REMOVESHOP; break;
            case 2 : _csvName = CSV_VENDOR_ADDSHOP; break;
        }
        if ( _csvName ) {
            let _vendorNum: number = VendorData_blxf.instance.getUnlockVendorNum_blxf();
            let _cfgDataList: any[] = CsvManager_blxf.instance.getCsvDataByName_blxf( _csvName );
            let _data: any = _cfgDataList.find(item => item.VendorNum == _vendorNum);
            if ( _data ) {
                let { ConsumeType, ConsumeNum } = _data;
                consumeType = Number(ConsumeType), consumeNum = Number(ConsumeNum);
            }
        }

        switch ( type ) {
            case 1 :
                // 第一次空间不足，弱引导免费卸货重开
                _isGui1 = this.onCheckTriggerRemoveRestart_blxf( consumeType, 0 );
                if ( _isGui1 ) consumeNum = 0;

                // 埋点
                this.onFailReportEvent_blxf();
                break;
        }

        PageManager_blxf.instance.loadCommonVendorPanel_blxf({ type, consumeType, consumeNum, _isGui1 });
    }

    /** 加载金币不足弹窗 */
    loadGoldVideoPanel_blxf () {
        // let _goldVideoNum: number = GameData_blxf.instance.getGoldVideoNum_blxf();
        // if ( _goldVideoNum <= 0 ) return;

        let _data: any = CsvManager_blxf.instance.getDecorationData_blxf( 1, 1 ) || {};
        let { isUnlock } = _data;
        if ( !isUnlock ) return;

        this.loadCommonVendorPanel_blxf( 9 );
    }

    /** 摊位列表补货 */
    onAddVendorShopList_blxf () {
        // 检测是否需要补货
        let _isShopNum: boolean = this.onCheckIsAddShopNum_blxf();
        if ( !_isShopNum ) return this.loadCommonVendorPanel_blxf( 2 );

        // 上报自定义事件
        this.onReportEvent_blxf();

        VendorData_blxf.instance.initAddShopData_blxf();
        VendorData_blxf.instance.initMustShopIdList_blxf();
        VendorData_blxf.instance.initAddShopIdList_blxf();

        this._addShopNum = VendorData_blxf.instance.getAddShopTotalNum_blxf();
        this._addShopFailNum = 0;

        PublicModule_blxf.isRemoveShop = false;
        
        let _unlockVendorIndex: number = 0, _addOkNum: number = 0;
        this.onAddVendorShop_blxf( _unlockVendorIndex, _addOkNum );

        this.onClearVendorMark_blxf();

        this.scheduleOnce(()=>{
            this.onCheckAutoPanel_blxf();
        }, 0.1)

        // 隐藏手指
        this.onHideHandnode_blxf();
    }

    /**
     * 摊位上货
     * @param unlockVendorIndex 上货摊位下标 
     * @returns 无返回值
     */
    onAddVendorShop_blxf ( unlockVendorIndex: number, _addOkNum: number, vendorIdList: number[] = [] ) {
        // 检测是否还有货
        let _isShopNum: boolean = this.onCheckIsAddShopNum_blxf();
        if ( !_isShopNum ) return;

        let unlockVendorIdList: number[] = VendorData_blxf.instance.getAddShopVendorIdList_blxf();
        let _vendorIdLen: number = unlockVendorIdList.length;
        
        // 随机摊位发货
        let _isGui: boolean = GameData_blxf.instance.getIsGuidance_blxf();
        if ( vendorIdList.length == 0 ) {
            vendorIdList = [ ...unlockVendorIdList ];
            if ( _isGui ) {
                vendorIdList.sort((a, b) => Math.random() - 0.5);
                // 复制
                vendorIdList = UtilsModule_blxf.onCopyList_blxf( vendorIdList );
            }
            // vendorIdList = vendorIdList.splice(0, this._addShopNum);
            // vendorIdList.sort((a, b) => a - b);
        }

        // 是否额外图标
        let { extraRatio } = ConfigModule_blxf;
        let isExtraIcon: boolean = NumModule_blxf.instance.isRatio_blxf( extraRatio );
        // 第4小关前不出鞭炮
        let _passNum: number = GameData_blxf.instance.getPassNum_blxf();
        if ( _passNum <= 4 ) isExtraIcon = false;

        // let _vendorId: number = unlockVendorIdList[ unlockVendorIndex ];
        let _vendorId: number = vendorIdList[ unlockVendorIndex ];
        let _isAddOk: boolean = this.onTouchAddShop_test( _vendorId, _addOkNum, isExtraIcon );
        _isAddOk = this.onTouchAddShop_test( _vendorId, _addOkNum, isExtraIcon );

        // 上货成功
        if ( _isAddOk ) {
            this.scheduleOnce(()=>{
                AudioModule_blxf.instance.playShopOkAudio_xft( _addOkNum );
            }, 0.05 * (_addOkNum + 1))

            _addOkNum += 1;
            this._addShopNum -= 1;

            this.updateBtnShopNum_blxf();
        } else {
            this._addShopFailNum += 1;
            UtilsModule_blxf.instance.Log_blxf(`摊位上货失败 vendorId => ${_vendorId}`);

            // 检测全部摊位商品是否已满
            let _isShopAll: boolean = this._addShopFailNum >= _vendorIdLen;
            if ( _isShopAll ) {
                _addOkNum == 0 && this.loadCommonVendorPanel_blxf( 1 );
                return UtilsModule_blxf.instance.Log_blxf(`已解锁摊位商品已满！！`, 2);
            }
        }

        // 下个摊位
        unlockVendorIndex += 1;

        // 摊位循环
        let _isMaxIndex: boolean = unlockVendorIndex == _vendorIdLen;
        if ( _isMaxIndex ) {
            unlockVendorIndex = 0;
            vendorIdList.length = 0;
            this._addShopFailNum = 0;
        }

        this._addShopNum == 0 && this.onAutoShop_blxf();
        // 递归上货
        this._addShopNum > 0 && this.onAddVendorShop_blxf( unlockVendorIndex, _addOkNum, vendorIdList );

        // 检测是否出现单个商品
        this._addShopNum <= 0 && VendorData_blxf.instance.onCheckVendorShop_blxf();
    }

    /** 卸货 */
    onRemoveVendorAllShop_blxf ( isRemove: boolean = false ) {
        PublicModule_blxf.isRemoveShop = isRemove;

        // 卸货音效
        AudioModule_blxf.instance.playAudio_blxf( EnumManager_blxf.gameAudioType.AUDIO_SHOP_DELET );

        this.vendorBox.children.forEach( item => {
            item.getComponent(VendorItem_blxf).onRemoveVendorAllShop_blxf();
        })

        // !isRemove && this.scheduleOnce(()=>{
        //     this.onCheckAllVendorAutoMove_blxf();
        // }, 0.2);

        this.scheduleOnce(()=>{
            this.onAutoShop_blxf();

            this.onHideHandnode_blxf( true );
        }, 0.2);
    }

    /** 手动添加商品 */
    onTouchAddShop_test ( _vendorId: number, addOkNum: number, isExtraIcon: any ) {
        // let _shopId: number = VendorData_blxf.instance.getTargetShopId_blxf();
        let _shopId: number = VendorData_blxf.instance.getTargetAddShopId_blxf( addOkNum );
        let _isAddOk: boolean = this.addVendorShop( _vendorId, _shopId, isExtraIcon );
        return _isAddOk;
    }

    /**
     * 添加摊位商品
     * @param vendorId 摊位id
     * @param shopId 商品id
     */
    addVendorShop ( vendorId: number, shopId: number, isExtraIcon: any, isShowSpine: boolean = false ) {
        let _isAddOk: boolean;
        this.vendorBox.children.forEach( item =>{
            let _itemThis = item.getComponent(VendorItem_blxf);
            let _isCheck: boolean = _itemThis.onCheckVendorId_blxf( vendorId );
            if ( !_isCheck ) return;

            _isAddOk = !!VendorData_blxf.instance.addVendorShop_blxf( vendorId, shopId, isExtraIcon, isShowSpine );
        })

        // _isAddOk && UtilsModule_blxf.instance.Log_blxf(`添加摊位商品: 摊位id & 商品id => ${vendorId} & ${shopId}`);

        return _isAddOk;
    }

    addVendorShop_diamond ( vendorId: number ) {
        let _markVendorData : BaseVendorData_blxf = VendorData_blxf.instance.findVendorData_blxf( vendorId );
        let _isVideoVendor: boolean = _markVendorData.onCheckVideoVendor_blxf();
        // 临时摊位不产生爆竹
        if ( _isVideoVendor ) return;

        let { diamondShopId } = ConfigModule_blxf;
        this.addVendorShop( vendorId, diamondShopId, false, true );
        // this.addVendorShop( vendorId, diamondShopId);

        // // 自动收集
        // this.scheduleOnce(()=>{
        //     this.onCheckAllVendorAutoMove_blxf();
        // }, 0.2);
    }

    /**
     * 检测客人
     * @param shopId 目标商品id 
     */
    onCheckGuest_blxf ( targetId: number, shopId: number ) {
        let _newShopId: number = VendorData_blxf.instance.getNewShopId_blxf();
        let _isNewShopId: boolean = !!_newShopId;

        // if ( _isNewShopId && shopId != _newShopId ) return;

        // this.guestBox.getComponent(GuestPanel_blxf).onCheckGuest_blxf( shopId, _isNewShopId );
        this.guestBox.getComponent(GuestPanel_blxf).updateGuestDialogue_blxf( targetId, shopId, _isNewShopId );
    }

    /**
     * 加载客人台词
     * @param dialogueType 台词类型
     */
    loadGuestDialogue_blxf ( targetId: number, dialogueType: string, isAnimation: boolean = false ) {
        this.guestBox.getComponent(GuestPanel_blxf).loadGuestDialogue_blxf( targetId, dialogueType, isAnimation );
    }

    /***** <<摊位相关操作逻辑>> start *****/

    /** 点击摊位 */
    onTouchVendor_blxf ( e: cc.Event.EventTouch, isBuy: boolean ) {
        if ( PublicModule_blxf.isPass && !isBuy ) return;

        let _vendorItemNode: cc.Node = e.currentTarget;
        let _vendorItemThis: VendorItem_blxf = _vendorItemNode.getComponent(VendorItem_blxf);
        let _vendorId: number = _vendorItemThis.getVendorId_blxf();

        // 解锁摊位
        let _isUnlockVendor: boolean = _vendorItemThis.onCheckUnlock_blxf();
        if ( !_isUnlockVendor ) return this.onUnlockVendor_blxf( _vendorItemThis );

        // 检测是否是Android
        let _isAndroid: boolean = cc.sys.os === cc.sys.OS_ANDROID;

        // 摊位可操作商品id
        let _vendorShopId: number = _vendorItemThis.onVendorShopId_blxf();
        // 是否有标记摊位
        let _isMark: boolean = VendorData_blxf.instance.onCheckMarkVendorId_blxf();
        
        // 1：未选择摊位，标记此摊位
        if ( !_isMark || isBuy ) {
            // 空摊位不标记
            if ( _vendorShopId == -1 || !_vendorShopId ) return;

            // 上报自定义事件
            this.onReportEvent_blxf();

            !_isAndroid && !isBuy && this.onVibrateShort_blxf();

            // 点击摊位音效
            AudioModule_blxf.instance.playAudio_blxf( EnumManager_blxf.gameAudioType.AUDIO_TOUCH_VENDOR );
            
            VendorData_blxf.instance.addMarkVendorId_blxf( _vendorId );

            this._vendorItemThis = _vendorItemThis;

            // 隐藏手指
            this.onHideHandnode_blxf( true && false );
            
            // 标记后自动收集爆竹
            let _markVendorData : BaseVendorData_blxf = VendorData_blxf.instance.findVendorData_blxf( _vendorId );
            let _isAuto: boolean = this.onCheckAutoMove_blxf( _markVendorData, _vendorItemThis );

            return !_isAuto && _vendorItemThis.onMarkShopUI_blxf();
        }

        // 点击摊位音效
        AudioModule_blxf.instance.playAudio_blxf( EnumManager_blxf.gameAudioType.AUDIO_TOUCH_VENDOR );

        // 再次点击标记摊位
        let _markVendorId: number = VendorData_blxf.instance.getMarkVendorId_blxf();
        UtilsModule_blxf.instance.Log_blxf(`标记摊位 & 目标摊位 >> ${_markVendorId} & ${_vendorId}`);
        if ( _vendorId == _markVendorId ) {
            !_isAndroid && this.onVibrateShort_blxf();

            // 隐藏手指
            this.onHideHandnode_blxf();
            return this.onClearVendorMark_blxf( false );
        }

        // 上报自定义事件
        this.onReportEvent_blxf();

        // 操作成功，将标记摊位可操作物品 移动至 点击摊位
        this.onUpdateVendorShop_blxf( _markVendorId, _vendorId, 0, _vendorItemThis, isBuy );
    }

    /** 清除摊位标记 */
    onClearVendorMark_blxf ( isAnimation: boolean = true, isAudio: boolean = false ) {
        VendorData_blxf.instance.clearMarkVendorId_blxf();

        this._vendorItemThis && this._vendorItemThis.onMarkShopUI_blxf( -1, isAnimation );
        this._vendorItemThis = null;

        isAnimation && isAudio && AudioModule_blxf.instance.playAudio_blxf( EnumManager_blxf.gameAudioType.AUDIO_TARGET_ERROR );
    }

    /**
     * 解锁摊位
     * @param vendorItemThis 摊位this
     */
    onUnlockVendor_blxf ( vendorItemThis: VendorItem_blxf, isAllUnlock: boolean = false ) {
        UtilsModule_blxf.instance.Log_blxf('执行解锁摊位逻辑！');

        let _vendorId: number = vendorItemThis.getVendorId_blxf();
        let _vendorData: BaseVendorData_blxf = VendorData_blxf.instance.findVendorData_blxf( _vendorId );
        // cc.log('_vendorData >>>', _vendorData);
        if ( !_vendorData ) return;

        let { unlockType, unlockNum } = _vendorData;

        // 分享解锁
        let _shareId: number = vendorItemThis.getShareId_blxf();
        let _isShare: boolean = vendorItemThis.onCheckIsShare_blxf();
        if ( _isShare ) {
            // 调用分享
            UtilsModule_blxf.onShareMessage( _shareId );
            // 分享监听
            cc.game.on(`onShareOK${ _shareId }_blxf`, ()=>{
                this.unlockVendorOk_blxf( vendorItemThis, _vendorData, true );
                // 保存分享id
                GameData_blxf.instance.setShareIdList_blxf( _shareId );
            }, this);
            return;
        }

        // 视频解锁
        let _isVideo: boolean = unlockType == EnumManager_blxf.gameNumType.NUM_VIDEO;
        if ( _isVideo ) {
            PlatformManager_blxf.instance.onPlayVideo_blxf(()=>{
                this.unlockVendorOk_blxf( vendorItemThis, _vendorData );

                _shareId && GameData_blxf.instance.setVideoIdList_blxf( _shareId )
            })
            return;
        }

        let _isNum = NumModule_blxf.instance.onCheckNum_blxf( unlockType, unlockNum, true );
        if ( _isNum ) _isNum = vendorItemThis._data.onCheckIsUnlockVendor_blxf( true );
        if ( !_isNum && !isAllUnlock ) {
            return UtilsModule_blxf.instance.Log_blxf(`解锁摊位失败，货币不足 unlockType & unlockNum ==> ${unlockType} & ${unlockNum}`, 2);
        }

        this.unlockVendorOk_blxf( vendorItemThis, _vendorData );
    }

    /** 解锁摊位成功 */
    unlockVendorOk_blxf ( vendorItemThis: VendorItem_blxf, vendorData: BaseVendorData_blxf, isShare: boolean = false ) {
        // 解锁音效
        AudioModule_blxf.instance.playAudio_blxf( EnumManager_blxf.gameAudioType.AUDIO_UNLOCK );

        let _vendorId: number = vendorItemThis.getVendorId_blxf();
        let { unlockType, unlockNum } = vendorData;

        // 扣除相应数量
        NumModule_blxf.instance.updateNumByType( unlockType, -unlockNum );
        // 解锁摊位
        GameData_blxf.instance.unlockVendor_blxf( _vendorId );

        VendorData_blxf.instance.newAddVendorIdList_blxf( _vendorId );
        vendorData.unlockVendor_blxf();
        
        // todo 解锁动画
        vendorItemThis.updateNode_blxf( false );
        PageManager_blxf.instance.loadSpineVendorUnlock_blxf(
            vendorItemThis.node, 0,
            ( spineSkeleton: sp.Skeleton, duration: number )=>{
                this.scheduleOnce(()=>{
                    vendorItemThis.updateUI_blxf();
                    cc.game.emit('onUpdateTopNum_blxf', unlockType);
                }, duration - 0.1);
            }
        )

        // 上报解锁摊位自定义事件
        this.onVendorReportEvent_blxf( _vendorId, isShare );
    }

    /** ( TODO ==>> 部分逻辑移可至 VendorData )
     * 标记摊位商品 移动至 目标摊位
     * @param targetVendorId 目标摊位id
     */
    onUpdateVendorShop_blxf ( markVendorId: number, targetVendorId: number, updateNum: number = 0, vendorItemThis: VendorItem_blxf, isBuy: boolean ) {
        let _markVendorData : BaseVendorData_blxf = VendorData_blxf.instance.findVendorData_blxf( markVendorId );
        let _targetVendorData : BaseVendorData_blxf = VendorData_blxf.instance.findVendorData_blxf( targetVendorId );
        let _markVendorShopId: number = VendorData_blxf.instance.onVendorShopId_blxf();
        let _targetVendorShopId: number = _targetVendorData.onCheckShopId_blxf();

        // UtilsModule_blxf.instance.Log_blxf(`《2》开始执行操作: 标记商品id & 目标商品id => ${_markVendorShopId} & ${_targetVendorShopId}`);

        // 2：已标记摊位，目标是摊位，检测摊位 是否没有商品 或 可操作商品是否和标记摊位可操作商品 一致
        let _isAlike: boolean = !_targetVendorShopId || _targetVendorShopId == -1 || _targetVendorShopId == _markVendorShopId;
        let _isAudio: boolean = updateNum == 0 && _targetVendorShopId && _targetVendorShopId != _markVendorShopId;
        if ( !_isAlike && !isBuy ) {
            // 隐藏手指
            this.onHideHandnode_blxf();
            return this.onClearVendorMark_blxf( true, _isAudio );
        }

        // 目标摊位最大可添加数
        let _addMaxShopNum: number = _targetVendorData.getMaxAddShopNum_blxf();
        if ( _addMaxShopNum <= 0 ) return this.onClearVendorMark_blxf( false );

        // 3: 移除标记摊位商品数据
        let _removeShopData: BaseShopData_blxf = _markVendorData.removeShop_blxf();
        if ( !_removeShopData ) return UtilsModule_blxf.instance.Log_blxf('移除标记摊位商品出错');

        // 计算位置数（暂未用到）
        let _maxRemoveNum: number = _markVendorData.getShopNumByShopId_blxf();
        if ( _maxRemoveNum > _addMaxShopNum ) _maxRemoveNum = _addMaxShopNum;
        let _addNum: number = _maxRemoveNum - updateNum;

        // 4: 添加目标摊位商品
        _targetVendorData.addShop_blxf( _removeShopData.shopId, false, _removeShopData.getIsExtraIcon_blxf() );
        let _isAllShop: boolean = _targetVendorData.onCheckIsAllShop_blxf();

        let _moveEndPos: cc.Vec3 = vendorItemThis.getNextShopEndPos_blxf( _addNum );
        // 移除标记摊位商品节点
        this.removeVendorNode_blxf( markVendorId, null, updateNum, ()=>{
            vendorItemThis.clearUpdateTimer_blxf();

            // 自动送货
            _isAllShop && this.onAutoShop_blxf();

            // this.scheduleOnce(()=>{
            //     this.onCheckAutoMove_blxf( _targetVendorData, vendorItemThis );
            // }, 0.2)
        }, _moveEndPos );

        // 隐藏手指
        updateNum == 0 && this.onHideHandnode_blxf();

        // 递归
        updateNum += 1;
        this.onUpdateVendorShop_blxf( markVendorId, targetVendorId, updateNum, vendorItemThis, isBuy );
    }

    /** 检测所有摊位自动收集 */
    onCheckAllVendorAutoMove_blxf () {
        this.vendorBox.children.forEach( vendorItem =>{
            let _vendorItemThis: VendorItem_blxf = vendorItem.getComponent( VendorItem_blxf );
            let _vendorId = _vendorItemThis._data.getVendorId_blxf();
            let _vendorData = VendorData_blxf.instance.findVendorData_blxf( _vendorId );
            this.onCheckAutoMove_blxf( _vendorData, _vendorItemThis );
        })
    }

    /**
     * 检测是否自动收集
     * @param targetVendorData 
     * @param vendorItemThis 
     * @param num 
     * @param flag 
     * @returns 
     */
    onCheckAutoMove_blxf ( targetVendorData: BaseVendorData_blxf, vendorItemThis: VendorItem_blxf, num: number = 0, flag: boolean = false ) {
        let _targetVendorShopId: number = targetVendorData.onCheckShopId_blxf();
        let _isAuto: boolean = _targetVendorShopId == ConfigModule_blxf.diamondShopId;
        if ( !_isAuto ) return;

        let _isAllShop: boolean = targetVendorData.onCheckIsAllShop_blxf();
        if ( !_isAllShop && !flag ) return;

        let _removeShopData: BaseShopData_blxf = targetVendorData.removeShop_blxf( num > 0 );
        if ( !_removeShopData ) return;

        num == 0 && this.onCoupletReward_blxf();

        // 移除标记摊位商品节点
        let _markVendorId = targetVendorData.getVendorId_blxf();
        this.removeVendorNode_blxf( _markVendorId, null, num, ()=>{
            vendorItemThis.clearUpdateTimer_blxf();

            this.onVibrateShort_blxf();

            // 清除标记
            num == 10 && this.onClearVendorMark_blxf( false );
        }, PublicModule_blxf.diamondIconPos, true );

        num += 1;
        this.onCheckAutoMove_blxf( targetVendorData, vendorItemThis, num, true );

        return true;
    }

    /** 对联奖励 */
    onCoupletReward_blxf () {
        let _coupletText: string = VendorData_blxf.instance.onRandomCoupletText_blxf();
        if ( !_coupletText ) return;

        PageManager_blxf.instance.loadCoupletAnimationPanel_blxf({ coupletText: _coupletText });
    }

    /** 移除标记摊位商品节点 */
    removeVendorNode_blxf ( vendorId: number, targetItemThis: TargetItem_blxf = null, num: number = 0, callback: any = ()=>{}, targetPos: cc.Vec3 = null, isAuto: boolean = false ) {
        // 物品移动落下音效
        let _isAudio: boolean = num % 2 == 0;
        // 检测是否是Android
        let _isAndroid: boolean = cc.sys.os === cc.sys.OS_ANDROID;
        targetPos && _isAudio && this.scheduleOnce(()=>{
            // !_isAndroid && AudioModule_blxf.instance.playAudio_blxf( EnumManager_blxf.gameAudioType.AUDIO_SHOP_DROP );
        }, 0.25 + num * 0.05)

        let _targetPos: cc.Vec3, _type: number = 1;
        if ( targetItemThis ) {
            _targetPos = UtilsModule_blxf.instance.getCanvasPos_blxf( targetItemThis.shopImgSpr.node );
        } else {
            _type = 2;
            _targetPos = targetPos;
        }

        let _isRemove: boolean = true;
        this.vendorBox.children.forEach( item => {
            let _itemThis: VendorItem_blxf = item.getComponent(VendorItem_blxf)
            let _itemVendorId = _itemThis.getVendorId_blxf();

            _isRemove = _itemVendorId == vendorId;
            _isRemove && _itemThis.removeShop_blxf( _targetPos, num, callback, _type, isAuto );
        })
    }

    /***** <<摊位相关操作逻辑>> end *****/



    /***** <<菜篮子相关操作逻辑>> start *****/

    onGuestTouchTarget_blxf ( guestId: number) {
        // 是否有标记摊位
        let _isMark: boolean = VendorData_blxf.instance.onCheckMarkVendorId_blxf();
        if ( !_isMark ) return;

        this.targetBox.children.forEach( targetNode =>{
            let _targetThis = targetNode.getComponent(TargetItem_blxf)
            let _targetId: number = _targetThis.getTargetId_blxf();
            if ( _targetId != guestId + 1 ) return;

            this.onTouchTarget_blxf({ currentTarget: targetNode });
        })
    }

    /** 点击菜篮子 */
    onTouchTarget_blxf ( e: any ) {
        let _targetItemNode: cc.Node = e.currentTarget;
        let _targetItemThis: TargetItem_blxf = _targetItemNode.getComponent(TargetItem_blxf);
        let _targetId: number = _targetItemThis.getTargetId_blxf();
        UtilsModule_blxf.instance.Log_blxf(`点击菜篮子: 菜篮子id => ${_targetId}`);

        // 解锁菜篮子
        let _isUnlockTarget: boolean = _targetItemThis.onCheckUnlock_blxf();
        if ( !_isUnlockTarget ) return this.onUnlockTarget_blxf( _targetItemThis );

        // 是否有标记摊位
        let _isMark: boolean = VendorData_blxf.instance.onCheckMarkVendorId_blxf();
        if ( !_isMark ) return;

        // // 上报自定义事件
        // this.onReportEvent_blxf();

        this._videoShopId = -1;
        this.onUpdateTarget_blxf( _targetId, _targetItemThis );
    }

    /**
     * 更新菜篮子
     * @param _targetId 菜篮子id
     * @param _targetItemThis 菜篮子对象
     * @returns 
     */
    onUpdateTarget_blxf ( _targetId: number, _targetItemThis: TargetItem_blxf, num: number = 0 ) {
        // 2：已标记摊位，目标是菜篮子，检测菜篮子是否需要此摊位可操作商品
        let _markVendorId: number = VendorData_blxf.instance.getMarkVendorId_blxf();
        let _markVendorData : BaseVendorData_blxf = VendorData_blxf.instance.findVendorData_blxf( _markVendorId );
        let _markVendorShopId: number = _markVendorData.onCheckShopId_blxf();
        let _touchTargetData: BaseTargetData_blxf = VendorData_blxf.instance.findTargetData_blxf( _targetId );

        // 标记摊位没有商品
        if ( !_markVendorShopId || _markVendorShopId == -1 ) {
            return this.onClearVendorMark_blxf();
        }

        // 标记临时菜篮子商品id
        let _targetType: number = _touchTargetData.getTargetType_blxf();
        let _isTarget: boolean = _targetType == 3;
        let _isVideoTarget: boolean = _targetType == 1;
        if ( _isVideoTarget ) {
            if ( this._videoShopId == -1 ) {
                this._videoShopId = _markVendorShopId;
            } else {
                let _isAlike: boolean = this._videoShopId == _markVendorShopId;
                if ( !_isAlike ) return this.onClearVendorMark_blxf();
            }
        }

        // 检测菜篮子是否已满
        let _isNeedShop: boolean = _touchTargetData.onCheckNeedShopNum_blxf( 1 );
        if ( !_isNeedShop ) {
            this.onClearVendorMark_blxf();
            return UtilsModule_blxf.instance.Log_blxf(`菜篮子已满: 菜篮子id => ${_targetId}`);
        }

        let _isInitBuyShopId: boolean = _touchTargetData.onCheckInitNormalTarget_blxf();
        if ( _isInitBuyShopId ) {
            // 更新菜篮子商品id
            _touchTargetData.onUpdateShopId_blxf( _markVendorShopId );
            // 更新菜篮子商品ui
            _targetItemThis.updateShop_blxf();
        }

        // 检测标记商品是否可以放入菜篮子
        let _isBuyShop: boolean = _touchTargetData.onCheckShopId_blxf( _markVendorShopId );
        if ( !_isBuyShop ) {
            this.onClearVendorMark_blxf( true, false );

            // 错误台词、音效
            let _isError: boolean = num == 0;
            if ( _isError ) {
                /*_isTarget &&*/ this.loadGuestDialogue_blxf( _targetId, EnumManager_blxf.guestDialogueType.DIALOGUE_ANGRY );
                AudioModule_blxf.instance.playAudio_blxf( EnumManager_blxf.gameAudioType.AUDIO_TARGET_ERROR );
            }

            return UtilsModule_blxf.instance.Log_blxf(`放入菜篮子失败: 标记摊位id & 标记商品id & 菜篮子id => ${_markVendorId} & ${_markVendorShopId} & ${_targetId}`);
        }

        /** todo new add 是否需要集齐商品 */
        let _isNeedAllShop: boolean = ConfigModule_blxf.isNeedAllShop;
        if ( _isNeedAllShop && num == 0 && !_isVideoTarget ) {
            let _isAllShop: boolean = _markVendorData.onCheckIsAllShop_blxf();
            if ( !_isAllShop ) {
                this.onClearVendorMark_blxf();
                return UtilsModule_blxf.onTips_blxf( EnumManager_blxf.tipsType.TIPS_TARGET_ERROR );
            }
        }

        // 3: 移除标记摊位商品数据
        let _removeShopData: BaseShopData_blxf = _markVendorData.removeShop_blxf( num > 0 );
        if ( !_removeShopData ) return !num && UtilsModule_blxf.instance.Log_blxf('移除标记摊位商品出错');

        let _shopId: number = _removeShopData.getShopId_blxf();
        let _isExtraIcon = _removeShopData.getIsExtraIcon_blxf();

        this.scheduleOnce(()=>{
            AudioModule_blxf.instance.playShopOkAudio_xft( num );
        }, 0.45 + num * 0.05)
        this.scheduleOnce(()=>{
            this.onVibrateShort_blxf();
        }, 0.45 + num * 0.02)
        
        let _addMaxShopNum: number = _touchTargetData.getMaxShopNum_blxf();

        // 4: 添加目标菜篮子商品数
        let _isAll: boolean = _touchTargetData.addBuyShopNum_blxf( 1 );
        let _nowShopNum: number = _touchTargetData.getBuyShopNum_blxf();

        // 台词
        /*_isAll && _isTarget &&*/ this.loadGuestDialogue_blxf( _targetId, EnumManager_blxf.guestDialogueType.DIALOGUE_OK, !_isTarget || !_isAll );

        // 移除标记摊位商品节点
        this.removeVendorNode_blxf( _markVendorId, _targetItemThis, num, ()=>{
            let _isVideoVendor: boolean = _markVendorData.onCheckVideoVendor_blxf();
            let _vendorId: number = !_isVideoVendor ? _markVendorId : VendorData_blxf.instance.getNullVendorId_blxf();
            _isExtraIcon && _vendorId && this.addVendorShop_diamond( _vendorId );

            // 5: 更新菜篮子节点UI
            _targetItemThis.updateNum_blxf( _nowShopNum );

            // 更新关卡进度
            let _isNeedTarget: boolean = _touchTargetData.getTargetType_blxf() != 1;
            _isAll && this.onCheckTargetReward_blxf( _addMaxShopNum, _isNeedTarget, 0, _shopId, _markVendorId, _targetId );
            // _isAll && cc.game.emit('onUpdateTopNum_blxf');
            _isAll && !_isVideoTarget && cc.game.emit('onUpdateTopPassInfo_blxf');
            /*_isAll &&*/ num == 1 && AudioModule_blxf.instance.playAudio_blxf( EnumManager_blxf.gameAudioType.AUDIO_TARGET_OK );
            // // todo 元宝
            // !_isVideoTarget && num == 1 && this.addVendorShop_diamond( _markVendorId );

            _isAll && this.scheduleOnce(()=>{
                // 检测加载客人
                let _isLoadGuest: boolean = _targetType == 3 || _targetType == 2;
                // _isLoadGuest && this.onCheckGuest_blxf( _touchTargetData.getBuyShopId_blxf() );

                // 检测解锁新客人
                let _touchTargetShopId: number = !_isLoadGuest ? -1 : _touchTargetData.getBuyShopId_blxf();
                _isLoadGuest && this.onCheckUnlockGuest_blxf( _markVendorShopId, _touchTargetShopId, _targetId );

                // 检测进阶奖励
                this.scheduleOnce( ()=>{ this.onCheckPassRewardPanel_blxf( _touchTargetData, _touchTargetShopId ); }, 0.5);

                // 检测是否出现单个商品
                VendorData_blxf.instance.onCheckVendorShop_blxf();

                // 检测菜篮子升级
                let _isTargetLv: boolean = _touchTargetData.onCheckTargetLevel_blxf();

                !_isTargetLv && _targetItemThis.updateShopData_blxf( _isTargetLv );

                _isTargetLv && PageManager_blxf.instance.loadSpineTargetLvUp_blxf( 
                    _targetItemThis.node, 0,
                    ( spineSkeleton: sp.Skeleton, duration: number )=>{
                        this.scheduleOnce(()=>{
                            _targetItemThis.updateShopData_blxf( _isTargetLv );
                        }, duration - 0.5)

                        // 升级音效
                        AudioModule_blxf.instance.playAudio_blxf( EnumManager_blxf.gameAudioType.AUDIO_NEW );
                });
            }, 0.15)
        });
        
        // 递归
        num += 1;
        !_isAll && this.onUpdateTarget_blxf( _targetId, _targetItemThis, num );

        _isAll && this.onClearVendorMark_blxf( false );
    }

    /**
     * 检测解锁新客人
     * @param shopId 商品id
     */
    onCheckUnlockGuest_blxf ( shopId: number, touchTargetShopId: number, targetId: number ) {
        // let _newShopId: number = VendorData_blxf.instance.getNewShopId_blxf();
        // if ( !_newShopId || _newShopId != shopId ) {
            return !PublicModule_blxf.isPass && this.onCheckGuest_blxf( targetId, touchTargetShopId );
        // }

        // let _shopData: any = VendorData_blxf.instance.findShopData_blxf( shopId );
        // if ( !_shopData ) return;

        // // 目标菜篮子商品已是新商品，重置新商品
        // GameData_blxf.instance.setNewShopId_blxf();

        // let { NewGuestId } = _shopData;
        // if ( !NewGuestId ) return this.onCheckGuest_blxf( targetId, touchTargetShopId );

        // let _guestData: any = VendorData_blxf.instance.getGuestInfo_blxf( NewGuestId );
        // if ( !_guestData ) return;

        // // 喜爱物品相关数据
        // let _newGuestData = VendorData_blxf.instance.getGuestInfo_blxf( NewGuestId );
        // let { LikeShopId } = _newGuestData;
        // let _likeShopData: any = CsvManager_blxf.instance.getShopData_blxf( LikeShopId );
        // let { ShopName, AtlasName, ImgName, SellNum } = _likeShopData;

        // let _isPass: boolean = PublicModule_blxf.isPass;
        // let _data: object = {
        //     shopPath : AtlasName, shopImgName: ImgName, shopName: ShopName, shopSellNum: SellNum,
        //     pageType  : 1, ..._guestData, _closeCB: ()=>{
        //         !_isPass && this.onCheckGuest_blxf( targetId, touchTargetShopId );

        //         PublicModule_blxf.isMoveAnimation = true;
        //         GameData_blxf.instance.unlockGuestId_blxf( Number(NewGuestId) );
        //     }
        // };
        // PageManager_blxf.instance.loadQueuePage_blxf( _data );
    }

    /**
     * 检测进阶奖励
     * @param touchTargetData 菜篮子数据
     */
    onCheckPassRewardPanel_blxf ( touchTargetData: BaseTargetData_blxf, touchTargetShopId: number = null ) {
        if ( !PublicModule_blxf.isPass ) return;

        PublicModule_blxf.isPass = false;

        // this._passTargetId = touchTargetData.targetId;

        // /** 加载奖励弹窗 */
        // let _passShopInfo: any = touchTargetData.getPasShopInfo_blxf();
        // this.loadNewRewardPanel_blxf( _passShopInfo, touchTargetShopId );

        // // 更新菜篮子关卡商品数据
        // VendorData_blxf.instance.initPassShopInfo_blxf();

        // // 小关埋点
        // this.onSmallPassReportEvent_blxf();
    }

    /**
     * 加载奖励弹窗
     * @param passShopInfo 关卡商品信息
     */
    loadNewRewardPanel_blxf ( passShopInfo: any, touchTargetShopId: number ) {
        if ( passShopInfo == -1 ) return;
        let { ShopId, NewGuestId } = passShopInfo;
        let _shopId = Number( ShopId );
        let _guestId = Number( NewGuestId );

        let _passNum = GameData_blxf.instance.getPassNum_blxf();
        let _isPass = _passNum % ConfigModule_blxf.basePassNum == 1;
        
        if ( _guestId ) {
            // let _guestData: any = VendorData_blxf.instance.getGuestInfo_blxf( _guestId );
            // let _data: object = { 
            //     pageType  : 1, ..._guestData
            // };
            // PageManager_blxf.instance.loadQueuePage_blxf( _data );
        }

        if ( _shopId ) {
            this._touchTargetShopId = touchTargetShopId;
            
            _isPass && PublicModule_blxf.onWealthDataList_blxf();

            let { ShopName, AtlasName, ImgName, SellNum, WealthNum } = passShopInfo;
            let _data: object = { 
                pageType : 2,
                shopName : ShopName,
                path     : `${AtlasName}`,
                imgName  : ImgName,
                SellNum, WealthNum,
                _closeCB : ()=>{
                    this.onCheckPass_blxf( _isPass );
                }
            };
            PageManager_blxf.instance.loadQueuePage_blxf( _data );
        } else {
            // this.onCheckPass_blxf( _isPass );
            this.loadRewardPanel_blxf( passShopInfo, _isPass );
        }

        this.onTriggerGC_blxf();
    }

    /** 加载奖励弹窗 */
    loadRewardPanel_blxf ( passShopInfo: any, _isPass: boolean ) {
        let { IsCommon, RewardType, RewardNum } = passShopInfo;
        if ( IsCommon != 1 ) return;

        let _data: any = {
            titleText  : '获得奖励',
            rewardType : RewardType,
            rewardNum  : RewardNum,
            _touchCB   : ( touchPos: cc.Vec3 ) =>{
                this.onCheckPass_blxf( _isPass );

                cc.game.emit('onUpdateTopPassInfo_blxf', true);

                NumModule_blxf.instance.updateNumByType( Number(RewardType), Number(RewardNum), touchPos );
            }
        }
        PageManager_blxf.instance.loadRewardPanel_blxf( _data );
    }

    /** 检测是否通过一大关 */
    onCheckPass_blxf ( _isPass: boolean ) {
        if ( !_isPass ) return this.onNewShopCheckGuest_blxf();

        let _bigPassNum = GameData_blxf.instance.getBigPassNum_blxf();
        let _diamondNum: number = NumModule_blxf.instance.getNumByType( 2 );
        let _shareId: number = 3;
        let _isShare: boolean = !GameData_blxf.instance.onCheckShareId_blxf( _shareId );

        let _data: any = {
            passNum  : _bigPassNum - 1,
            diamondNum : _diamondNum,
            shareId : _shareId, isShare: _isShare,
            _closeCB : () =>{
                // OpenDataContext_blxf.offOpenData_blxf();
                // PublicModule_blxf.isGuestAudio = true;

                // this.onNewShopCheckGuest_blxf();

                // cc.game.emit('onTouchRemoveShop_blxf');
                // cc.game.emit('onTouchRestartShop_blxf'); 

                // GameData_blxf.instance.setBigPassNum_blxf();

                this.loadNextPanel( _bigPassNum );

                // 清空
                PublicModule_blxf.onUpdateIsTriggerNegative_blxf( false );
            }
        }
        PageManager_blxf.instance.loadPassPanel_blxf( _data );

        // 完成大关上报事件
        this.onBigPassReportEvent_blxf( _bigPassNum - 1 );
    }

    /**
     * 加载下关面板
     * @param bigPassNum 下一大关 
     */
    loadNextPanel ( bigPassNum: number ) {
        let _isLvUp: boolean = bigPassNum > 1;
        let _options: any = {
            passNum  : bigPassNum,
            _closeCB : () =>{
                PublicModule_blxf.isGuestAudio = true;

                this.onNewShopCheckGuest_blxf();

                // cc.game.emit('onTouchRemoveShop_blxf');
                cc.game.emit('onTouchRestartShop_blxf'); 
                cc.game.emit('onUpdateTopPassInfo_blxf', true);

                _isLvUp && this.scheduleOnce(()=>{
                    // 视频摊位重新上锁
                    this.onRestartVideoVendor_blxf();
                }, 0.5)

                GameData_blxf.instance.setBigPassNum_blxf();

                // 摊位升级
                _isLvUp && PageManager_blxf.instance.loadVendorLvUpPanel_blxf();
            }
        }
        PageManager_blxf.instance.loadNextPassList_blxf( _options );
    }

    // 视频摊位重新上锁
    onRestartVideoVendor_blxf () {
        VendorData_blxf.instance.onRestartVideoVendor_blxf();

        if ( !this.vendorBox ) return;
        this.vendorBox.children.forEach( vendorItem =>{
            let _vendorItemThis: VendorItem_blxf = vendorItem.getComponent(VendorItem_blxf);
            _vendorItemThis.updateUI_blxf();
        })
    }

    /** 获取新商品后检测客人 */
    onNewShopCheckGuest_blxf () {
        let _isShopId: boolean = this._touchTargetShopId && this._touchTargetShopId != -1;
        _isShopId && this.onCheckGuest_blxf( this._passTargetId, this._touchTargetShopId );
    }

    /**
     * 检测菜篮子奖励
     * @param shopNum 集满商品数
     * @returns 
     */
    onCheckTargetReward_blxf ( shopNum: number, isNeedTarget: boolean = false, ratio: number = 0, shopId: number, markVendorId: number, targetId: number = -1 ) {
        let _rewardData: any = CsvManager_blxf.instance.getTargetRewardByNum_blxf( shopNum );
        if ( !_rewardData ) return;

        let _ratio: number = isNeedTarget ? 1 : 0.5;
        if ( ratio > 0 ) _ratio = ratio;

        let _isLike: boolean = this.onCheckGuestLikeShop_blxf( targetId, shopId );
        let _guestRatio: number = _isLike ? 2 : 1;

        let { Reward1, Reward2 } = _rewardData;
        let [ iconTyp1, iconNum1 ] = Reward1.split('&');
        let [ iconTyp2, iconNum2 ] = Reward2.split('&');

        // 新奖励逻辑
        let _shopCfgData: any = CsvManager_blxf.instance.getShopData_blxf( shopId );
        if ( !_shopCfgData ) return;

        // 获取摊位坐标
        let vendorNode = this.vendorBox.children.find( itemNode =>{
            let _itemThis: VendorItem_blxf = itemNode.getComponent(VendorItem_blxf)
            let _itemVendorId = _itemThis.getVendorId_blxf();
            return _itemVendorId == markVendorId;
        })
        let _toP = UtilsModule_blxf.instance.getCanvasPos_blxf( vendorNode );

        let { baseGoldNum } = ConfigModule_blxf;
        let { SellNum, WealthNum } = _shopCfgData;
        let _vendorLv = GameData_blxf.instance.getVendorLv_blxf( markVendorId );

        iconNum1 = SellNum * shopNum * _guestRatio + baseGoldNum * _vendorLv;
        iconNum2 = WealthNum * shopNum;

        iconNum1 = Math.round( iconNum1 * _ratio );
        iconNum2 = Math.round( iconNum2 * _ratio );
        NumModule_blxf.instance.updateNumByType( Number(iconTyp1), iconNum1, _toP );
        NumModule_blxf.instance.updateNumByType( Number(iconTyp2), iconNum2, _toP );

        // 文字动画
        this.onNumTween_blxf( Number(iconTyp1), iconNum1, _toP.add(cc.v2( 0,  20 - 50 )) );
        this.onNumTween_blxf( Number(iconTyp2), iconNum2, _toP.add(cc.v2( 0, -20 - 50 )) );
    }

    /** 检测是否是客人喜欢的商品 */
    onCheckGuestLikeShop_blxf ( targetId: number, shopId: number ) {
        let _isLike: boolean;

        let _index = targetId - 2;
        let _guestData = PublicModule_blxf.targetGuestIds[ _index ];
        if ( !_guestData ) return _isLike;

        _isLike = _guestData.LikeShopId == shopId;
        return _isLike;
    }

    // 文字动画
    onNumTween_blxf ( type: number, iconNum: number, _toP: cc.Vec3 ) {
        let _numStr: string, _numStr2: string;
        switch ( type ) {
            case 1 : _numStr = `到账`, _numStr2 = `+${iconNum}`; break;
            case 2 : _numStr = `财富+${iconNum}`; break;
        }
        // 货币数动画
        PageManager_blxf.instance.onIconNumAnimation_blxf( _numStr, _toP, _numStr2 );
    } 

    /** 检测自动解锁菜篮子 */
    onCheckAutoUnlockTarget_blxf ( isAllUnlock: boolean = false ) {
        this.targetBox.children.forEach( targetItem =>{
            let _targetItemThis = targetItem.getComponent( TargetItem_blxf );
            if ( !_targetItemThis ) return;

            let _isUnlockTarget: boolean = _targetItemThis.onCheckUnlock_blxf();
            if ( _isUnlockTarget ) return;

            let _isLoadAnimation = _targetItemThis.getIsLoadAnimation_blxf();
            if ( !_isLoadAnimation && !isAllUnlock ) return;
            this.onUnlockTarget_blxf( _targetItemThis, isAllUnlock );
        })
    }

    /** 解锁菜篮子 */
    onUnlockTarget_blxf ( targetItemThis: TargetItem_blxf, isAllUnlock: boolean = false ) {
        UtilsModule_blxf.instance.Log_blxf('执行解锁菜篮子逻辑！');

        let _targetId: number = targetItemThis.getTargetId_blxf();
        let _targetData: BaseTargetData_blxf = VendorData_blxf.instance.findTargetData_blxf( _targetId );
        if ( !_targetData ) return;

        let { unlockType, unlockNum } = _targetData;

        let _isVideo: boolean = unlockType == EnumManager_blxf.gameNumType.NUM_VIDEO;
        if ( _isVideo ) {
            PlatformManager_blxf.instance.onPlayVideo_blxf(()=>{
                this.unlockTargetOk_blxf( targetItemThis, _targetData, true );
            })

            // UtilsModule_blxf.onReportEvent_blxf( 2, 107, true );
            return;
        }
        let _isNum: boolean = _targetData.onCheckUnlock_blxf( true );
        if ( !_isNum && !isAllUnlock ) {
            return UtilsModule_blxf.instance.Log_blxf(`解锁菜篮子失败，货币不足 unlockType & unlockNum ==> ${unlockType} & ${unlockNum}`, 2);
        }

        this.unlockTargetOk_blxf( targetItemThis, _targetData );
    }

    /** 解锁菜篮子成功 */
    unlockTargetOk_blxf ( targetItemThis: TargetItem_blxf, targetData: BaseTargetData_blxf, isVideo: boolean = false ) {

        // 解锁音效
        AudioModule_blxf.instance.playAudio_blxf( EnumManager_blxf.gameAudioType.AUDIO_UNLOCK );

        let _targetId: number = targetItemThis.getTargetId_blxf();
        let _targetGameData: any = GameData_blxf.instance.getTargetData_blxf( _targetId );

        let { unlockType, unlockNum, targetType } = targetData;
        let _targetLv: number = _targetGameData ? _targetGameData.targetLv : 1;

        if ( !isVideo || !_targetGameData) {
            // // 扣除相应数量
            // NumModule_blxf.instance.updateNumByType( unlockType, -unlockNum );
            // 解锁菜篮子
            GameData_blxf.instance.unlockTarget_blxf( _targetId, targetType );

            VendorData_blxf.instance.newAddTargetIdList_blxf( _targetId );
        }

        targetData.unlockTarget_blxf();

        // todo 解锁动画
        targetItemThis.updateNode_blxf( false );
        PageManager_blxf.instance.loadSpineTargetUnlock_blxf( 
            targetItemThis.node, 0, 
            ( spineSkeleton: sp.Skeleton, duration: number )=>{
                this.scheduleOnce(()=>{
                    targetItemThis.updateUI_blxf();
                    targetItemThis.updateShopData_blxf( true );
                    cc.game.emit('onUpdateTopNum_blxf', unlockType);
                }, duration);
            }, _targetLv 
        );
    }

    /***** <<菜篮子相关操作逻辑>> end *****/


    /** 检测自动弹空间不足弹窗 */
    onCheckAutoPanel_blxf () {
        let _addShopMaxNum: number = VendorData_blxf.instance.getVendorAddShopMaxNum_blxf();
        let _isAll: boolean = _addShopMaxNum == 0;
        if ( !_isAll ) return;

        let _isMove: boolean = VendorData_blxf.instance.onCheckShopMove_blxf();
        if ( _isMove ) return;

        this.loadCommonVendorPanel_blxf( 1 );
    }

    
    /** 进入游戏 */
    onEntryGameClear_blxf () {
        PublicModule_blxf.isRemoveShop = true;

        VendorData_blxf.instance.onCheckConnectClear_blxf();

        this.vendorBox.children.forEach( vendorItem =>{
            let _vendorItemThis: VendorItem_blxf = vendorItem.getComponent(VendorItem_blxf);
            _vendorItemThis.onRemoveVendorAllShop_blxf();
        })

        this.targetBox.children.forEach( targetItem =>{
            let _targetItemThis: TargetItem_blxf = targetItem.getComponent( TargetItem_blxf );
            _targetItemThis.updateShopData_blxf();
        })
    }



    /** 检测满物品按钮动画 */
    onCheckAllShopBtn_blxf () {
        if ( this._allShopBtnTween ) return;
        if ( this._isAllShopGuestAnimation ) return;

        let { winSizeW, gameW, isIpad } = ConfigModule_blxf.instance;
        let _checkX: number = isIpad ? ( winSizeW - gameW ) / 2 : 0;
        let _updateX: number = 230 + _checkX, _t: number = 0.3;

        let _isAllShopTarget: boolean = this.onCheckAllShopVendor_blxf( -1 ) == 3;
        if ( _isAllShopTarget === this._isAllShopTarget ) return;

        if ( !_isAllShopTarget ) _updateX *= -1;

        _isAllShopTarget && this.onAllShopGuestAnimation_blxf( );
        this._allShopBtnTween = cc.tween( this.allShopTargetNode ).delay(0.5).by( _t, { x: _updateX }).call(()=>{
            this._isAllShopTarget = _isAllShopTarget;
            this._allShopBtnTween = null;

            PublicModule_blxf.isAllShopTarget = this._isAllShopTarget;
        }).start();

        // todo 已废弃
        // _isAllShopTarget && this.onCheckTriggerAllShopGuidance_blxf();
    }

    /**
     * 检测摊位是否是满商品且可操作
     * @param vendorId 摊位id
     * @returns 返回结果 1: 摊位未满、2: 满商品摊位是目标菜篮子商品、3: 满商品摊位可操作
     */
    onCheckAllShopVendor_blxf ( vendorId: number ) {
        let _triggerType: number = 1;
        
        let _vendorShopIdList: number[] = VendorData_blxf.instance.getVendorAllShopIdList_blxf( vendorId );
        let _vendorShopIdNum: number = _vendorShopIdList.length;
        if ( _vendorShopIdNum == 0 ) return _triggerType;

        let _isHave: boolean;
        let { _targetShopIdList, _isNullTarget } = VendorData_blxf.instance.getTargetAllShopIdList_blxf();
        _targetShopIdList.forEach( shopIdItem =>{
            if ( _isHave ) return;
            _isHave = _vendorShopIdList.includes( shopIdItem );
        })

        // 摊位集齐物品 有不是 篮子目标物品
        let _isCheck: boolean;
        _vendorShopIdList.forEach( shopIdItem =>{
            if ( _isCheck ) return;
            _isCheck = !_targetShopIdList.includes( shopIdItem );
        })
        if ( _isCheck ) _isHave = false;

        // 是否有空篮子 且 无目标物品
        if ( _isNullTarget ) _isHave = true;

        _triggerType = !_isHave ? 3 : 2;

        return _triggerType;
    }

    /**
     * 点击低价收购
     * @param e 按钮点击数据
     * @param isTouchBtn 是否是点击送货调用
     */
    onTouchAllShopTarget_blxf ( e: cc.Event.EventTouch, isTouchBtn: boolean = false ) {
        // 是否有标记摊位
        let _isMark: boolean = VendorData_blxf.instance.onCheckMarkVendorId_blxf();
        if ( !_isMark ) return;

        let _checkNum = 10;
        
        let _markVendorId: number = VendorData_blxf.instance.getMarkVendorId_blxf();
        let _markVendorData : BaseVendorData_blxf = VendorData_blxf.instance.findVendorData_blxf( _markVendorId );

        let _triggerType: number = this.onCheckAllShopVendor_blxf( _markVendorId );

        if ( _triggerType != 3 && !isTouchBtn ) {
            let { TIPS_RECOVERY_MSG1, TIPS_RECOVERY_MSG2 } = EnumManager_blxf.tipsType;
            UtilsModule_blxf.onTips_blxf( _triggerType == 1 ? TIPS_RECOVERY_MSG1 : TIPS_RECOVERY_MSG2 );
            AudioModule_blxf.instance.playAudio_blxf( EnumManager_blxf.gameAudioType.AUDIO_TARGET_ERROR );
            return this.onClearVendorMark_blxf();
        }

        this.onRemoveAllShop_blxf( _markVendorData, _markVendorId, _checkNum );

        this.onAllShopGuestAnimation_blxf( 'happy' );

        // // 上报自定义事件
        // UtilsModule_blxf.onReportEvent_blxf( 1, 11 );
    }

    onRemoveAllShop_blxf ( markVendorData: BaseVendorData_blxf, vendorId: number, num: number ) {
        num -= 1;

        // 3: 移除标记摊位商品数据
        let _removeShopData: BaseShopData_blxf = markVendorData.removeShop_blxf();
        if ( !_removeShopData ) return UtilsModule_blxf.instance.Log_blxf('移除标记摊位商品出错');

        let _shopId: number = _removeShopData.getShopId_blxf();
        let _isExtraIcon: boolean = _removeShopData.getIsExtraIcon_blxf();

        this.scheduleOnce(()=>{
            this.onVibrateShort_blxf();
            AudioModule_blxf.instance.playShopOkAudio_xft( num );
        }, 0.45 + num * 0.05)

        let _targetPos: cc.Vec3 = this.allShopTargetNode.position;
        this.vendorBox.children.forEach( item => {
            let _itemThis: VendorItem_blxf = item.getComponent(VendorItem_blxf)
            let _itemVendorId = _itemThis.getVendorId_blxf();

            let _isRemove: boolean = _itemVendorId == vendorId;
            _isRemove && _itemThis.removeShop_blxf( _targetPos, num, ()=>{

                // todo 元宝
                _isExtraIcon && this.addVendorShop_diamond( vendorId );

                if ( num != 0 ) return;

                AudioModule_blxf.instance.playAudio_blxf( EnumManager_blxf.gameAudioType.AUDIO_TARGET_OK )

                // let _targetData = VendorData_blxf.instance.findTargetData_blxf( 3 );
                // _targetData.addPassShopNum_blxf( 10 );

                this.onCheckTargetReward_blxf( 10, false, 0.5, _shopId, vendorId );

                // 低价收购后
                this.guestBox.getComponent(GuestPanel_blxf).loadSmallPriceDialogue_blxf();

                GameData_blxf.instance.addLoveNum_blxf();

                let _pos: cc.Vec3 = UtilsModule_blxf.instance.getCanvasPos_blxf( item );
                cc.game.emit('loadLoveParticle_blxf', _pos);

                // // cc.game.emit('onUpdateTopNum_blxf');
                // // 不增加进度条
                // cc.game.emit('onUpdateTopPassInfo_blxf');

                // this.scheduleOnce( ()=>{ this.onCheckPassRewardPanel_blxf( _targetData ); }, 0.5);
            }, 1 );
        })

        num == 0 && this.onClearVendorMark_blxf( false );
        num > 0 && this.onRemoveAllShop_blxf( markVendorData, vendorId, num );
    }

    /** 自动送货 */
    onAutoShop_blxf () {
        this.scheduleOnce(()=>{
            this.onBuyAllMoveShop_blxf();
        }, 0.1);
    }

    /** 送货 */
    onBuyAllMoveShop_blxf () {
        let _buyNum: number = 0;

        // _targetInfo = { buyShopId: targetId }
        let _targetInfo: object = VendorData_blxf.instance.onTargetBuyShopIdInfo_blxf();

        // 清除标记摊位
        this.onClearVendorMark_blxf();

        // 检测摊位 -->> 菜篮、低价收购
        this.vendorBox.children.forEach( vendorItem =>{
            let _vendorThis = vendorItem.getComponent( VendorItem_blxf );

            let _isUnlock: boolean = _vendorThis._data.onCheckUnlockVendor_blxf();
            if ( !_isUnlock ) return;

            let _isAllShop: boolean = _vendorThis._data.onCheckIsAllShop_blxf();
            if ( !_isAllShop ) return;

            let _shopId: number = _vendorThis._data.onCheckShopId_blxf();
            // // 鞭炮商品不参与送货
            // if ( _shopId == ConfigModule_blxf.diamondShopId ) return;

            let _targetId: number = _targetInfo[ _shopId ];
            // UtilsModule_blxf.instance.Log_blxf([ '_shopId: ', _shopId, _targetId ]);

            let _event: any = { currentTarget: vendorItem };
            this.onTouchVendor_blxf( _event, true );

            if ( _targetId ) {
                _targetInfo[ _shopId ] = null;

                let _targetItemNode: cc.Node = this.targetBox.children.find( targetItem =>{
                    let _targetThis = targetItem.getComponent( TargetItem_blxf );
                    return _targetId == _targetThis.getTargetId_blxf();
                })
                this.onTouchTarget_blxf({ currentTarget: _targetItemNode });
            } else {
                this.onTouchAllShopTarget_blxf( null, true );
            }

            _buyNum += 1;
        })

        // // 不可送货提示
        // _buyNum == 0 && UtilsModule_blxf.onTips_blxf( EnumManager_blxf.tipsType.TIPS_NOT_BUY_SHOP );

        // 连击动画
        _buyNum >= 2 && this.loadComboAnimation_blxf( _buyNum );

        // 提交3个物品之后所有货架全部开放
        this._totalBuyNum += _buyNum;
        this._totalBuyNum >= 3 && this.onUnlockAllUI_blxf();

        // 上报自定义事件
        this.onReportEvent_blxf();
    }

    onTriggerGC_blxf () {
        this.scheduleOnce(()=>{
            window['wx'] && window['wx'].triggerGC();
        }, 3)
    }

    // 连击动画
    loadComboAnimation_blxf ( comboNum: number = 2 ) {
        if ( comboNum > 8 ) comboNum = 8;

        this.scheduleOnce(()=>{
            PageManager_blxf.instance.loadSpineCombo_blxf( `${comboNum}` );
        }, 0.3);
    }


    /** 检测触发满物品引导 */
    onCheckTriggerAllShopGuidance_blxf () {
        if ( this.node.x < 0 ) return;

        let _isGuiAllShop: boolean = GameData_blxf.instance.getIsGuidanceAllShop_blxf();
        if ( _isGuiAllShop ) return;
        
        PageManager_blxf.instance.loadGuidance_blxf( 2 );
        this.onClearVendorMark_blxf();
    }

    /** 检测触发卸货重装弱引导 */
    onCheckTriggerRemoveRestart_blxf ( consumeType: number, consumeNum: number ) {
        let _isTrigger: boolean = GameData_blxf.instance.getIsGuiRemoveRestart_blxf();
        if ( _isTrigger ) return;

        _isTrigger = NumModule_blxf.instance.onCheckNum_blxf( consumeType, consumeNum );

        return _isTrigger;
    }

    /** 检测菜篮升级 */
    onCheckTargetLvUp_blxf () {
        this.targetBox.children.forEach( targetItem =>{
            let _targetThis = targetItem.getComponent(TargetItem_blxf);
            if ( !_targetThis ) return;

            let _targetLv: number = _targetThis.getTargetLv_blxf();

            _targetThis.initTargetLvUpData_blxf();

            let _targetLv2: number = _targetThis.getTargetLv_blxf();
            if ( _targetLv == _targetLv2 ) return;

            // // 加载升级动画
            // PageManager_blxf.instance.loadSpineTargetLvUp_blxf( 
            //     targetItem, 0,
            //     ( spineSkeleton: sp.Skeleton, duration: number )=>{
            //         // 升级音效
            //         AudioModule_blxf.instance.playAudio_blxf( EnumManager_blxf.gameAudioType.AUDIO_DRAGON_EXP );
            // });

            _targetThis.updateBgImg_blxf();
        })
    }

    /**
     * 获取满物品可操作摊位坐标
     * @param cb 回调函数
     */
    onAllShopVendorPos_blxf ( cb: any ) {
        let _vendorIdList: number[] = VendorData_blxf.instance.getVendorAllShopIdList_blxf( -1, true );
        let _vendorId: number = _vendorIdList[0];
        let _vendorNode: cc.Node = this.vendorBox.children.find( vendorItem =>{
            let _itemVendorId: number = vendorItem.getComponent(VendorItem_blxf).getVendorId_blxf();
            return _itemVendorId == _vendorId;
        })

        let { x, y } = UtilsModule_blxf.instance.getCanvasPos_blxf( _vendorNode );
        cb && cb( x, y );
    }

    // /** 检测自动售卖升级 */
    // onAutoCheckTargetLvUp_blxf () {
    //     this.targetBox.children.forEach( targetItem =>{
    //         let _targetThis = targetItem.getComponent(TargetItem_blxf);
    //         if ( !_targetThis ) return;

    //         let _targetLv: number = _targetThis.getTargetLv_blxf();

    //         _targetThis.initTargetLvUpData_blxf();

    //         let _targetLv2: number = _targetThis.getTargetLv_blxf();
    //         cc.log('_targetLv >>', _targetLv, _targetLv2);
    //         if ( _targetLv == _targetLv2 ) return;

    //         // 加载升级动画
    //         PageManager_blxf.instance.loadSpineTargetLvUp_blxf( 
    //             targetItem, 0,
    //             ( spineSkeleton: sp.Skeleton, duration: number )=>{
    //                 // 升级音效 AUDIO_DRAGON_EXP
    //                 AudioModule_blxf.instance.playAudio_blxf( EnumManager_blxf.gameAudioType.AUDIO_NEW );
    //         });

    //         _targetThis.updateBgImg_blxf();
    //     })
    // }

    /** 震动 */
    onVibrateShort_blxf () {
        let _isOffVibrate: boolean = GameData_blxf.instance.getIsOffVibrate_blxf();
        !_isOffVibrate && PlatformManager_blxf.instance.onVibrateShort_blxf();
    }

    /** 上报自定义事件 */
    onReportEvent_blxf () {
        // let _isGui: boolean = GameData_blxf.instance.getIsGuidance_blxf();
        // if ( _isGui && this._reportEventId != 7 ) return;

        // this._reportEventId += 1;
        // UtilsModule_blxf.onReportEvent_blxf( 1, this._reportEventId );
    }


    /**
     * 上报解锁摊位自定义事件
     * @param vendorId 摊位id
     */
    onVendorReportEvent_blxf ( vendorId: number, isShare: boolean = false ) {
        // let _eventId: number;
        // switch ( Number(vendorId) ) {
        //     case 5 : _eventId = isShare ? 109 : 108; break;
        // }

        // _eventId && UtilsModule_blxf.onReportEvent_blxf( 2, _eventId, true );

        // let _vendorNum: number = VendorData_blxf.instance.getUnlockVendorNum_blxf();
        // UtilsModule_blxf.onReportEvent_blxf( 2, 1000 + _vendorNum, true );
    }

    /**
     * 完成大关上报事件
     * @param bigPassNum 大关数
     */
    onBigPassReportEvent_blxf ( bigPassNum: number ) {
        UtilsModule_blxf.onReportEvent_blxf( 1, 150 + bigPassNum );
    }

    /** 过关埋点 */
    onSmallPassReportEvent_blxf () {
        // 过关埋点
        let _eventData: any = UtilsModule_blxf.instance.onReportEventData_blxf( 1 );
        UtilsModule_blxf.onReportEvent_blxf( 2, 307, false, _eventData );

        let _passNum: number = GameData_blxf.instance.getPassNum_blxf();
        if ( _passNum > 6 ) return;

        // 小关埋点
        let _n1: number = Math.ceil( (_passNum - 1) / ConfigModule_blxf.basePassNum );
        let _n2: number = (_passNum - 1) % ConfigModule_blxf.basePassNum;
        _n2 != 0 && UtilsModule_blxf.onReportEvent_blxf( 1, 100 + _n1 * 10 + _n2 );
    }

    /** 上报失败所用时间 */
    onFailReportEvent_blxf () {
        // 第一次失败
        UtilsModule_blxf.instance.onFristReportEvent_blxf( 2, 303 );

        let _eventData: any = UtilsModule_blxf.instance.onReportEventData_blxf( 1 );
        UtilsModule_blxf.onReportEvent_blxf( 2, 305, false, _eventData );
    }


    /** 解锁所有客人和物品 */
    onUnlockGuestAndShop_blxf () {
        let { CSV_GUEST, CSV_SHOP } = EnumManager_blxf.instance.getGameCsvType();
        // 客人全解锁
        let _cfgGuestList: any[] = CsvManager_blxf.instance.getCsvDataByName_blxf( CSV_GUEST );
        _cfgGuestList.forEach( item =>{
            let { GuestId } = item;
            let _guestId: number = Number( GuestId );
            
            if ( _guestId > 6 ) return;

            _guestId < 100 && GameData_blxf.instance.unlockGuest_blxf( _guestId );
            _guestId < 100 && GameData_blxf.instance.unlockGuestId_blxf( _guestId );
        })

        // 物品全解锁
        let _shopCfgList = CsvManager_blxf.instance.getCsvDataByName_blxf( CSV_SHOP );
        _shopCfgList.forEach( item =>{
            let { ShopId } = item;
            let _shopId: number = Number( ShopId );

            if ( _shopId > 10 ) return;

            GameData_blxf.instance.unlockShop_blxf( _shopId );
        })
    }

    // 解锁所有摊位、菜篮
    onUnlockAllUI_blxf () {
        // 解锁所有客人和物品
        this.onUnlockGuestAndShop_blxf();

        // 解锁所有摊位
        this.vendorBox.children.forEach( vendorItem =>{
            let _vendorItemThis: VendorItem_blxf = vendorItem.getComponent(VendorItem_blxf);
            let _isUnlockVendor: boolean = _vendorItemThis.onCheckUnlock_blxf();
            !_isUnlockVendor && this.onUnlockVendor_blxf( _vendorItemThis, true );
        })

        // 解锁所有菜篮
        this.onCheckAutoUnlockTarget_blxf( true );

        let _passShopNum: number = GameData_blxf.instance.getPassShopNum_blxf();
        GameData_blxf.instance.setPassShopNum_blxf( _passShopNum, true );

        VendorData_blxf.instance.initAddShopData_blxf();
        VendorData_blxf.instance.initAddShopIdList_blxf();

        this._addShopNum = VendorData_blxf.instance.getAddShopTotalNum_blxf();
    }

    /** 手指引导倒计时 */
    onTimer_demo ( dt: number ) {
        if ( PublicModule_blxf.isGui ) {
            return this._handTimer = 0.5;
        }

        if ( this._handTimer < 0 ) return;
        if ( this.handItemNode.active ) return;

        this._handTimer -= dt;
        if ( this._handTimer > 0 ) return;

        this._handTimer = -1;
        this.onGuidanceTouch_demo();
    }

    // 检测弱引导
    onGuidanceTouch_demo () {
        let _touchNode: cc.Node;
        let _dataList: any[] = this.onVendorDataList_demo();
        let _markVendorShopId: number = this._vendorItemThis ? VendorData_blxf.instance.onVendorShopId_blxf() : null;
        if ( !_markVendorShopId ) {
            let _totalNum: number = 0;
            // 没有标记摊位，引导可移动物品
            let _itemList: any[] = [];
            _dataList.forEach( item =>{
                let { vendorId, vendorItem, shopId, shopNum, shopIdNum } = item;

                let _isGT: boolean = false;
                let _item: any = _itemList.find( item1 => {
                    if ( !shopId ) return;
                    let _isCheck: boolean = !item1.shopId && shopIdNum > 1 || item1.shopId == shopId;
                    if ( _isCheck ) {
                        let _addNum: number = shopNum > item1.nullNum ? item1.nullNum : shopNum;
                        let _num: number = item1.shopNum + _addNum;
                        if ( _num == 10 || _num > _totalNum ) {
                            _totalNum = _num; 
                            _isGT = true;
                        }
                    }
                    return _isCheck;
                });
                if ( _item ) {
                    if ( _touchNode && !_isGT ) return;
                    _touchNode = vendorItem;
                } else {
                    _itemList.push( item );
                }
            })
        } else {
            let _touchData: any;
            let _markShopIdNum: number = this._vendorItemThis._data.getShopIdNum_demo();
            let _markNullNum: number = this._vendorItemThis._data.maxNum - this._vendorItemThis._data.getShopNum_blxf();
            // 有标记摊位，引导可合并物品
            _dataList.forEach( item =>{
                let { vendorId, vendorItem, shopId, shopNum, isMark, isMax, shopIdNum } = item;

                if ( isMax ) return;
                if ( isMark ) return;
                if ( shopId != _markVendorShopId ) return;
                if ( _touchNode && shopNum <= _touchData.shopNum ) return;
                let _isCheck: boolean = shopNum > _markNullNum;
                if ( _isCheck && shopIdNum > 1 && _markNullNum > 1 ) {
                    cc.log(`无效摊位移动 ${this._vendorItemThis.getVendorId_blxf()}==>>${vendorId}`);
                    return;
                }
                _touchNode = vendorItem;
                _touchData = item;
            })

            // 移动至空摊位
            !_touchNode && _markShopIdNum > 1 && _dataList.forEach( item =>{
                if ( _touchNode ) return;
                let { vendorItem, shopId, isMark, isMax, shopIdNum } = item;

                if ( shopId ) return;
                _touchNode = vendorItem;
            })
        }

        // 没有摊位可引导点击, 引导点击上货
        if ( !_touchNode ) {
            _touchNode = this.addShopBtn;
        }

        let _touchPos: cc.Vec3 = UtilsModule_blxf.instance.getCanvasPos_blxf( _touchNode );
        this.onGuidanceTween_blxf( _touchPos );
    }

    /** 获取摊位数据列表 */
    onVendorDataList_demo () {
        let _dataList: any[] = [];
        this.vendorBox.children.forEach( vendorItem =>{
            let _vendorItemThis: VendorItem_blxf = vendorItem.getComponent(VendorItem_blxf);
            let _isUnlockVendor: boolean = _vendorItemThis.onCheckUnlock_blxf();
            if ( !_isUnlockVendor ) return;

            let _vendorId: number = _vendorItemThis.getVendorId_blxf();
            let _vendorShopId: number = _vendorItemThis.onVendorShopId_blxf();
            let _vendorShopNum: number = _vendorItemThis._data.getShopNumByShopId_blxf();
            let _shopIdNum: number = _vendorItemThis._data.getShopIdNum_demo();
            let _isMark: boolean = _vendorItemThis._data.onCheckIsMark_blxf();
            let _isMax: boolean = _vendorItemThis.getShopNum_demo() == _vendorItemThis._data.maxNum;
            let _nullNum: number = _vendorItemThis._data.maxNum - _vendorItemThis._data.getShopNum_blxf();
            let _sortNum: number = _isMax ? -1 : _vendorId;
            _dataList.push({ 
                vendorId: _vendorId, vendorItem, shopId: _vendorShopId, shopNum: _vendorShopNum, shopIdNum: _shopIdNum, sortNum: _sortNum, nullNum: _nullNum,
                isMark: _isMark, isMax: _isMax 
            });
        })
        _dataList.sort((a, b) => {
            if ( b.shopIdNum == a.shopIdNum ) {
                return b.sortNum - a.sortNum;
            } else {
                return a.shopIdNum - b.shopIdNum;
            }
        });
        // cc.log('_dataList >>', _dataList);
        return _dataList;
    }

    /** 手指动画 */
    onGuidanceTween_blxf ( pos: cc.Vec3 ) {
        this.handItemNode.active = true;
        this.handItemNode.position = pos;
    }

    /** 隐藏手指 */
    onHideHandnode_blxf ( isCheck: boolean = false ) {
        this.handItemNode.active = false;

        this.initHandTimer_blxf( isCheck );
    }

    /** 重置倒计时 */
    initHandTimer_blxf ( isCheck: boolean ) {
        // isCheck = true; // todo test
        this._handTimer = isCheck ? 0.5 : 3;
    }

}
